/* Copyright (c) 2009-2010, Sean A.O. Harney <sharney3@gmail.com> */

//abstract statement list (no exprs in OMF)

#include "omf.h"

/* globals */
LLIST_P _asl_cells = NULL;	//todo move initialization
extern int yylineno;



LLIST_P asl_prepend(LLIST_P asl, ASL_NODE_P stmt)
{
    return llist_prepend(stmt, sizeof(struct st_asl_node), asl);
}

LLIST_P asl_append(LLIST_P asl, ASL_NODE_P stmt)
{
    return llist_append(stmt, sizeof(struct st_asl_node), asl);
}

bool asl_add_new_asl(char *symname, LLIST_P asl)
{
    struct st_asl_cell *asl_cell;

    asl_cell = checked_malloc(sizeof(struct st_asl_cell));

    asl_cell->symname = symname;
    asl_cell->asl = asl;

    //TODO: check symbol not in list
    _asl_cells = llist_append(asl_cell, sizeof(struct st_asl_cell), _asl_cells);	//c string, length not needed
    if (_asl_cells == NULL)
	return false;

    debug2_printf("Added symbol: %s\n", symname);
    return true;
}

//notused
LLIST_P asl_get_asl(char *symname)
{
    struct st_asl_cell *asl_cell = asl_get_asl_cell(symname);

    if (asl_cell == NULL)
	return NULL;
    return asl_cell->asl;
}

struct st_asl_cell *asl_get_asl_cell(char *symname)
{
    LLIST_P walker;
    struct st_asl_cell *asl_cell;

    for (walker = _asl_cells; walker != NULL; walker = walker->next)
      {
	  asl_cell = walker->element;
	  if (!strcmp(asl_cell->symname, symname))
	      return asl_cell;
      }
    return NULL;
}

void asl_print(FILE * fp, LLIST_P asl)
{
    LLIST_P walker;
    ASL_NODE_P stmt;

    if (asl != NULL)
      {
	  for (walker = asl; walker != NULL; walker = walker->next)
	    {
		stmt = walker->element;
		fprintf(fp, "\t %d\t%s()\n",
			stmt->lineno, stmt_type_to_str(stmt->type));
	    }
    } else
	fprintf(fp, "List is empty.\n");
    fflush(fp);

}

void asl_print_all(FILE * fp)
{
    LLIST_P walker;
    struct st_asl_cell *asl_cell;

    for (walker = _asl_cells; walker != NULL; walker = walker->next)
      {
	  asl_cell = walker->element;
	  fprintf(fp, "ASL[%s]\n", asl_cell->symname);
	  asl_print(fp, asl_cell->asl);
      }
}
